#include "UserService.h"
#include <QDebug>
#include <QtSql/QSqlDatabase>
#include <QtSql/QSqlError>
#include "dao/UserDao.h"
#include "helper/SessionGuard.h"
#include "helper/ConnectionPool.h"
#include "helper/CryptHelper.h"
#include "helper/AuthManager.h"

UserService::UserService(QObject* parent): QObject(parent) {}

QString UserService::hashPassword(const QString& password) const
{
    return CryptHelper::sm3Hash(password.toUtf8()).toHex();
}

void UserService::login(const QString& username, const QString& password)
{
    try
    {

        // 使用 RAII 守卫自动管理会话
        SessionGuard guard;
        QSqlDatabase db = guard.database();

        const QString inputHash = hashPassword(password);

        auto user = UserDao::findByUsername(db, username);
        if (!user.has_value())
        {
            emit loginResult(false, tr("账户不存在"));
            return;  // 自动回滚（RAII）
        }

        if (user->userStatus != "ENABLE")
        {
            emit loginResult(false, tr("账户已被禁用"));
            return;
        }

        if (user->password != inputHash)
        {
            emit loginResult(false, tr("密码错误"));
            return;
        }

        auto userInfo = UserDao::getUserById(db, user->id);
        AuthManager::getInstance()->login(userInfo.value());

        if (!UserDao::updateLoginTime(db, user->account))  // 使用当前db对象
        {
            emit loginResult(false, tr("系统错误"));
            return;
        }

        // 显式提交事务
        // guard.commit();

        emit loginResult(true, tr("登录成功"));
        emit AuthManager::getInstance()->userChanged();
        emit AuthManager::getInstance()->authChanged(true);
    }
    catch (const QSqlError& e)  // 修正异常类型
    {
        qCritical() << "[Service] Database error:" << e.text();
        emit loginResult(false, tr("数据库错误"));
    }
    catch (const std::exception& e)
    {
        qCritical() << "[Service] System error:" << e.what();
        emit loginResult(false, QString::fromLocal8Bit(e.what()));
    }
}

void UserService::logout()
{
    AuthManager::getInstance()->logout();
}

SysUser UserService::currentUser() const
{
    return AuthManager::getInstance()->currentUser();
}
